<template>
  <basic-dialog
    title="经营品类"
    width="85%"
    :visible="dialogVisible"
    :handleClose="handleCancel"
    :showFooter="false"
  >
    <el-row class="business_category_body">
      <el-col :span="12" class="left-col">
        <div class="category-search">
          <el-form size="mini" ref="formData" :model="formData" inline>
            <el-form-item prop="categoryName" label="名称">
              <el-input
                placeholder="请输入品类名称"
                v-model="formData.categoryName"
                @keyup.enter.native="handleSerach"
              ></el-input>
            </el-form-item>
            <el-form-item prop="categoryName" label="编码">
              <el-input
                placeholder="请输入四级类编码"
                v-model="formData.categoryNo"
                @keyup.enter.native="handleSerach"
              ></el-input>
            </el-form-item>
            <el-form-item>
              <el-button type="primary" @click="handleSerach">查询</el-button>
            </el-form-item>
          </el-form>
        </div>
        <el-divider class="divider" content-position="left">条件查询结果：</el-divider>
        <div class="category-searchlist">
          <el-checkbox-group v-model="searchList.checkList" v-loading="searchLoading">
            <el-checkbox
              v-for="item in searchList.dataSource"
              :label="item.categoryUuid"
              :key="item.categoryUuid"
              @change="(val) => { handleCheckSearchList(val, item) }"
            >
            {{ item.categoryPath }}&nbsp;&nbsp;{{ item.categoryNo }}
            </el-checkbox>
          </el-checkbox-group>
        </div>
        <el-divider content-position="left">品类树选择</el-divider>
        <div class="el_tree_wrap category-tree">
          <el-tree
            ref="elTree"
            lazy
            accordion
            show-checkbox
            :node-key="elTree.nodeKey"
            :data="elTree.dataSource"
            :props="elTree.props"
            :load="loadElTreeNode"
            @check="getCheckedNodes"
          ></el-tree>
        </div>
      </el-col>
      <el-col :span="12">
        <div v-show="hasCheckedNodes">
          <el-divider content-position="right">
            <el-button size="large" type="text" @click="handleClear">清空</el-button>
            <el-button size="large" type="text" @click="handleOk">确定</el-button>
          </el-divider>
          <ShowCategoryTags
            closable
            :dataSource="checkedEndNodes"
            :handleDelete="handleDeleteTag"
          />
        </div>
      </el-col>
    </el-row>
  </basic-dialog>
</template>
<script>
import BasicDialog from '@/components/BasicDialog';
import ShowCategoryTags from './ShowCategoryTags';
import {
  queryCategoryListService,
  queryLevel4CategoryPathListService
} from '@/api/supplier/components';
import { isResponseSuccess } from '@/pages/supplier/utils/bizUtils';
import { ApiRequest } from '@api/basePage';

export default {
  components: {
    BasicDialog,
    ShowCategoryTags
  },
  props: {
    visible: {
      type: Boolean,
      default: false
    },
    categoryUuids: { // 品类uuid集合
      type: Array,
      default () { return []; }
    }
  },
  data () {
    return {
      dialogVisible: false,
      elTree: {
        dataSource: [], // 数据源
        props: {
          children: 'children',
          label: 'categoryName',
          disabled: 'disabled',
          isLeaf: 'leaf',
          checked: false
        },
        nodeKey: 'categoryNo',
        END_LEVEL: '4',
      },
      checkedEndNodes: [], // 已勾选展示四级类集合
      formData: {
        categoryName: '',
        categoryNo: '',
      },
      searchLoading: false,
      searchList: { // 查询列表
        dataSource: [], // 数据源
        checkList: [], // 勾选对象
      },
      selectCategoryIdInfo: {}, // 品类树勾选结果
      getCategoryListByKey: {
        url: '/sysback/choose/category/searchCategoryList',
        type: 'post'
      },
    }
  },
  computed: {
    // 有已选择品类数据
    hasCheckedNodes () {
      return this.checkedEndNodes.length > 0;
    }
  },
  watch: {
    visible (val) {
      this.dialogVisible = val;
      if (val) { // 进入弹框根据品类uuid查询已选择品类数据
        this.getShowCategoryResults({ level4Uuids: this.categoryUuids }, true);
      }
    }
  },
  methods: {
    // 加载el-tree节点
    loadElTreeNode (nodeData, resolve) {
      const { data, level } = nodeData;
      this.getCategoryListByLevel(level + 1, data.uuid).then(res => {
        resolve(this.getElTreeData(res.result?.records));
      });
    },
    // 表单-分类名称查询
    async handleSerach () {
      const data = {};
      const { categoryNo, categoryName } = this.formData;
      if (!categoryNo && !categoryName) {
        this.$message.warning('品类名称和品类编码不能同时为空');
        return false;
      }
      const { url, type } = this.getCategoryListByKey;
      const param = categoryNo ? `categoryNo=${categoryNo}` : `categoryName=${categoryName}`;
      const apiUrl = `${url}?${param}`;
      this.searchLoading = true;
      const res = await ApiRequest(apiUrl, type, data, true);
      this.searchLoading = false;
      if (res.retStatus == 1) {
        this.searchList.checkList = [];
        this.searchList.dataSource = res.retData;
      }
    },
    // 根据品类等级查询品类集合
    async getCategoryListByLevel (levelNum, parentUuid) {
      const data = {
        levelNum,
        parentUuid,
        categoryType: 2, // 查询供应商和公共品类
        nowPage: 1,
        pageShow: 10000,
      }
      let loadingInstance = this.$loading({ target: '.business_category_body' });
      const res = await queryCategoryListService(data);
      loadingInstance.close();
      return res;
    },
    // 获取一级分类集合
    async getOneLevelList () {
      const res = await this.getCategoryListByLevel(1);
      if (isResponseSuccess(res)) {
        this.elTree.dataSource = this.getElTreeData(res.result?.records);
      }
    },
    // 获取el-tree数据
    getElTreeData (list = []) {
      return list.filter(ele => ele.categoryName != '特殊供应商').map(item => ({
        ...item,
        disabled: item.levelNum === '1',
        leaf: item.levelNum === this.elTree.END_LEVEL
      }));
    },
    // 获取已勾选的节点
    getCheckedNodes (current, checked) {
      const { checkedNodes } = checked;
      const data = {
        level2Uuids: this.getCheckedUuidsByLevel(checkedNodes, 2),
        level3Uuids: this.getCheckedUuidsByLevel(checkedNodes, 3),
        level4Uuids: this.getCheckedUuidsByLevel(checkedNodes, 4),
      }
      this.selectCategoryIdInfo = data;
      this.getShowCategoryResults();
    },
    // 根据level获取对应勾选uuid集合
    getCheckedUuidsByLevel (list, level) {
      return list.filter(item => item.levelNum == level).map(item => item.uuid);
    },
    // 获取展示品类四级类结果
    async getShowCategoryResults (data, isInit) {
      if (!data) {
        const { level4Uuids = [] } = this.selectCategoryIdInfo;
        data = {
          ...this.selectCategoryIdInfo,
          level4Uuids: level4Uuids.concat(this.searchList.checkList)
        }
      }
      let loadingInstance = this.$loading({ target: '.business_category_body' });
      const res = await queryLevel4CategoryPathListService(data);
      loadingInstance.close();
      if (res) {
        if (isInit) { // 初次进入弹框，给初始化数据赋值
          this.initSelectedData = res.result
        } else {
          this.updateInitData(res.result);
        }
        this.setCurrentCheckedData(res.result);
      }
    },
    // 删除tag
    handleDeleteTag (tagInfo) {
      if (this.searchList.checkList.length) {
        const { categoryUuid } = tagInfo;
        this.searchList.checkList = this.searchList.checkList.filter(item => item != categoryUuid)
      }
      this.deleteCheckedCategory(tagInfo[this.elTree.nodeKey]); // 移除当前展示结果
      this.$refs.elTree.setChecked(tagInfo[this.elTree.nodeKey], false); // 取消el-tree对应四级类节点
    },
    // 删除已选品类
    deleteCheckedCategory (categoryNo) {
      const results = this.checkedEndNodes.filter(
        item => item[this.elTree.nodeKey] !== categoryNo
      );
      this.initSelectedData = results;
      this.setCurrentCheckedData(results);
    },
    // 清空选择结果
    handleClear () {
      this.$confirm('确定后将清空所有已选四级分类，您确认吗？', '清空', {
        type: 'warning',
      }).then(() => {
        this.checkedEndNodes = []; // 清空当前展示结果
        this.clearAllCheckedNodes();
        this.initSelectedData = []; // 清空初始选择数据
        this.closeAllExpandNodes();
        this.searchList.checkList = []; // 清空查询结果勾选集合
        this.selectCategoryIdInfo = {
          level2Uuids: [],
          level3Uuids: [],
          level4Uuids: [],
        };
      }).catch(() => {});
    },
    // 设置当前已勾选数据
    setCurrentCheckedData (data) {
      const concatList = [].concat(this.initSelectedData, _.cloneDeep(data));
      this.checkedEndNodes = _.uniqBy(concatList, this.elTree.nodeKey);
    },
    // 更新初始化已选择数据（当再次勾选该节点对应数据时，从初始化数据中移除）
    updateInitData (list) {
      this.initSelectedData = this.initSelectedData.filter(
        item => !list.find(node => node[this.elTree.nodeKey] === item[this.elTree.nodeKey])
      );
    },
    // 清空所有已勾选节点的勾选状态
    clearAllCheckedNodes () {
      this.$refs.elTree.setCheckedKeys([]); // 全部取消el-tree勾选节点
    },
    // 关闭所有已展开节点
    closeAllExpandNodes () {
      var nodes = this.$refs.elTree.store.nodesMap;
      for (let i in nodes) {
        nodes[i].expanded = false;
      }
    },
    // 确定
    handleOk () {
      this.$emit('getCheckedCategory', {
        source: this.checkedEndNodes,
        uuids: this.checkedEndNodes.map(item => item.categoryUuid),
        names: this.checkedEndNodes.map(item => item.categoryName),
        paths: this.checkedEndNodes.map(item => item.categoryPath),
      });
      this.closeDialog();
    },
    // 取消
    handleCancel () {
      this.closeDialog();
    },
    // 关闭弹框
    closeDialog () {
      this.$emit('update:visible', false);
      this.checkedEndNodes = [];
      this.clearAllCheckedNodes();
      this.closeAllExpandNodes();
    },
    // 条件查询勾选
    handleCheckSearchList () {
      this.getShowCategoryResults();
    },
  }
}
</script>
<style lang="less" scoped>
.left-col {
  border-right: 1px dashed #dadada;
  padding-right: 20px;
}
.category-searchlist {
  .el-checkbox-group {
    border: 1px solid #ebeef5;
    padding-left: 5px;
    height: 200px;
    max-height: 200px;
    overflow-y: auto;
    label {
      line-height: 24px;
      &:first-child {
        margin-top: 10px;
      }
      &:last-child {
        margin-bottom: 10px;
      }
    }
  }
}
.el_tree_wrap {
  max-height: 300px;
  overflow-x: hidden;
  overflow-y: scroll;
}
/deep/ .category-tree {
  height: 400px !important;
  overflow: auto;
  margin: 10px 0px;
  border: 1px solid #ebeef5;
}
</style>
